/*************************************************************************
	> File Name: ./include/ObjectPool.h
	> Author: zq
	> Mail: zhouquan1511@163.com 
	> Created Time: Wed 26 Apr 2023 09:29:12 PM CST
 ************************************************************************/

#pragma once

#include "Common.h"

inline static void* SystemAlloc(size_t kpage);
static void*& NextObj(void *ptr);

//定长内存池
template<class T>
class ObjectPool {
private:
	char *_memory = nullptr; //指向大块内存的指针
	size_t _remainBytes = 0; //大块内存切分后剩余的字节数
	void *_freeList = nullptr; //自由链表头，维护离散的小块定长内存
public:
	//申请对象
	T* New() {
		T *obj = nullptr;
		if (_freeList != nullptr) {
			obj = (T*)_freeList;
			_freeList = NextObj(_freeList);
		} else {
			size_t objsize = sizeof(T) < sizeof(void*) ?
							sizeof(void*) : sizeof(T);
			if (_remainBytes < objsize) {
				_remainBytes = 128 * 1024;
				_memory = (char*)SystemAlloc(_remainBytes>>13);
				if (_memory == nullptr)
					throw std::bad_alloc();
			}
			obj = (T*)_memory;
			_memory += objsize;
			_remainBytes -= objsize;
		}
		new(obj)T;
		
		return obj;
	}

	//释放对象
	void Delete(T *obj) {
		obj->~T();

		NextObj(obj) = _freeList;
		_freeList = obj;
	}
};

